/*
 * 
 *  This file is part of Sourceprojects.org Thracia.
 *  Copyright 2010 noctarius
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *    http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 * 
 */
package org.sourceprojects.thracia.util;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.net.URL;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.security.CodeSource;

import org.sourceprojects.thracia.report.beans.ClassbaseType;

/**
 * @author noctarius
 * 
 */
public class ClassbaseHelper {
	public static final String getClassbase(Class<?> clazz) {
		final CodeSource source = clazz.getProtectionDomain().getCodeSource();

		if (source != null) {
			String path = source.getLocation().getFile();

			if ((path.startsWith("/"))
					&& (path.charAt(2) == ":".toCharArray()[0]))
				path = path.substring(1);

			return path;
		}

		return "not found";
	}

	public static final ClassbaseType getClassbaseType(Class<?> clazz) {
		final CodeSource source = clazz.getProtectionDomain().getCodeSource();

		if (source == null)
			return ClassbaseType.Unknown;

		final URL url = source.getLocation();
		final File file = new File(url.getFile());

		if (!file.exists())
			return ClassbaseType.Unknown;

		if (file.isDirectory())
			return ClassbaseType.ClassDirectory;

		if (file.getName().endsWith(".class"))
			return ClassbaseType.MainClassFile;

		return ClassbaseType.JarCabinet;
	}

	private final Class<?> clazz;

	public ClassbaseHelper(Class<?> clazz) {
		this.clazz = clazz;
	}

	public String digest() throws FileNotFoundException, IOException {
		final CodeSource source = clazz.getProtectionDomain().getCodeSource();

		if (source == null) {
			throw new FileNotFoundException("Source not found");
		}

		URL url = source.getLocation();
		File file = new File(url.getFile());

		if (!file.exists())
			throw new FileNotFoundException(
					"JAR file or class directory not found in filesystem");

		if (file.isDirectory()) {

			url = new URL(source.getLocation().getProtocol() + "://"
					+ source.getLocation().getPath()
					+ clazz.getName().replace(".", "/") + ".class");
			file = new File(url.getFile());

			if (!file.exists()) {
				throw new FileNotFoundException(
						"JAR file or class directory not found in filesystem");
			}
		}

		final FileInputStream fis = new FileInputStream(file);
		final FileChannel fc = fis.getChannel();

		final byte[] data = new byte[(int) (fc.size())];

		final ByteBuffer bb = ByteBuffer.wrap(data);
		fc.read(bb);

		return SHA1.getSha1(data);
	}
}
